package com.itheima.app.manager;

import cn.hutool.core.bean.BeanException;
import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.io.FileUtil;
import cn.hutool.core.util.StrUtil;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.util.StringUtils;
import com.alibaba.fastjson.JSON;
import com.github.tobato.fastdfs.domain.conn.FdfsWebServer;
import com.github.tobato.fastdfs.domain.fdfs.StorePath;
import com.github.tobato.fastdfs.service.FastFileStorageClient;
import com.itheima.app.exception.BusinessException;
import com.itheima.app.interceptor.UserHolder;
import com.itheima.autoconfig.oss.OssTemplate;
import com.itheima.domain.db.UserInfo;
import com.itheima.domain.mongo.Sound;
import com.itheima.domain.vo.SoundVo;
import com.itheima.service.db.UserInfoService;
import com.itheima.service.mongo.SoundService;
import org.apache.dubbo.config.annotation.DubboReference;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.annotation.Reference;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Component;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.beans.BeanUtils;


import java.io.IOException;
import java.time.Duration;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.List;
import java.util.concurrent.TimeUnit;

@Component
public class SoundManager {
    @DubboReference
    private SoundService soundService;

    @Autowired
    private FastFileStorageClient client;

    @Autowired
    private FdfsWebServer webServer;

    @DubboReference
    private UserInfoService userInfoService;

    @Autowired
    private StringRedisTemplate stringRedisTemplate;


    //发送语音
    public void saveSound(MultipartFile soundFile)throws IOException {

        //1.获取登录用户id
        Long userId = UserHolder.get().getId();
        System.out.println(userId);
        //2. 语音上传fastsfs
        StorePath storePath = client.uploadFile(soundFile.getInputStream(),
                soundFile.getSize(), FileUtil.extName(soundFile.getOriginalFilename()), null);
        String voiceUrl = webServer.getWebServerUrl() + storePath.getFullPath();

        //3.注入userInfo查询个人信息
        UserInfo userInfo = userInfoService.findByUserId(userId);
        System.out.println(userInfo);

        // 从redis中查询数据   得到返回值
        String remainingTimes = stringRedisTemplate.opsForValue().get(StrUtil.format(userInfo.getId()+"RemainingTimes"));

        // 如果返回值是null
        if (remainingTimes == null) {

            // 说明登录用户是第一次发送 语音消息 那么我们就给redis中添加一个数值为9的数据 刷新时间为一天
            stringRedisTemplate.opsForValue().set(StrUtil.format(userInfo.getId()+"RemainingTimes"), "9", Duration.ofDays(1));

            // 如果返回值是0
        } else if (remainingTimes.equals("0")) {

            // 说明用户的使用次数已经用完 直接返回
            throw new BusinessException("今日次数已用完");

        } else {

            // 说明用户还有使用次数  正常使用 但每使用一次 在redis中的数值就会自减一
            stringRedisTemplate.opsForValue().decrement(userInfo.getId()+"RemainingTimes");

        }

        //4.创建Voice对象并赋值
        Sound sound = new Sound();
        sound.setUserId(userId.intValue());
        sound.setAvatar(userInfo.getAvatar());
        sound.setNickname(userInfo.getNickname());
        sound.setGender(userInfo.getGender());
        sound.setAge(userInfo.getAge());
        sound.setSoundUrl(voiceUrl);

        // 给voice对象的次数设置为redis中的次数
        sound.setRemainingTimes(Integer.parseInt(stringRedisTemplate.opsForValue().get(userInfo.getId()+"RemainingTimes")));

        // 保存到mongo
        System.out.println(sound);
        soundService.saveSound(sound);




    }

    //接收语音
    public SoundVo getSound() {
        // 获取用户id
        Long userId = UserHolder.get().getId();

        // 到表中随机查询一个用户
        Sound sound = soundService.findOneSound(userId);

        UserInfo userInfo1 = userInfoService.findByUserId(userId);

        // 去redis中查询是否有此数据
        String RemainingCount = stringRedisTemplate.opsForValue().get(StrUtil.format(userInfo1.getId()+"RemainingCount"));

        // 判断数据
        if (RemainingCount == null) {

            // 说明登录用户是第一次发送 语音消息 那么我们就给redis中添加一个数值为8的数据 刷新时间为一天
            stringRedisTemplate.opsForValue().set(StrUtil.format(userInfo1.getId()+"RemainingCount"), "9", Duration.ofDays(1));

            // 如果返回值是0
        } else if (RemainingCount.equals("0")) {

            // 说明用户的使用次数已经用完 直接返回null
            return null;
        }

        // 那么说明用户还有使用次数  正常使用 但每使用一次 在redis中的数值就会自减一
        stringRedisTemplate.opsForValue().decrement(userInfo1.getId()+"RemainingCount");

        // 将查询回来的用户封装到Voicevo中
        SoundVo vo = new SoundVo();
        // 获得登录用户的id
        UserInfo userInfo = userInfoService.findByUserId(sound.getUserId().longValue());

        // 将用户信息赋值到viocevo中
        BeanUtil.copyProperties(userInfo, vo);

        // 不同的字段单独赋值  这里是语音的地址
        vo.setSoundUrl(sound.getSoundUrl());

        // 从redis中获取到用户剩余的次数
        String remainingCount = stringRedisTemplate.opsForValue().get(userInfo1.getId()+"RemainingCount");

        // 再将获取到的用户剩余的次数 赋值给次数字段
        vo.setRemainingTimes(Integer.parseInt(remainingCount));

        // 最后返回这个vo
        return vo;

    }

}

